import React from "react";
import {Modal, Button, Checkbox, Icon} from "tinper-bee";
import Tree from "bee-tree";
const TreeNode = Tree.TreeNode;
import 'bee-tree/build/Tree.css';
import FormControl from "bee-form-control";
import 'bee-form-control/build/FormControl.css';
import "./index.less";
import Table from "bee-table";
import 'bee-table/build/Table.css';
import multiSelect from "bee-table/build/lib/multiSelect";
const MultiSelectTable = multiSelect(Table, Checkbox);

//referType : "tree" ||"table"||“multiSelectTable”||“multiSelectTree”
class CommonTreeReferStruc extends React.Component {
    constructor(props) {
        super(props);
        this.state = {
            showModal :false,
            hasSelectedValue : '',
            hasSelectedPk : '',
            inputValue :'',
            selectedKeysId: [],
            selectedKeysName :[],
            sname : "sname",
            scode : "scode",
            pk :"",
            isShowSearchArea : true,
            children : "children",
            title :'参照列表',
            selectedKeysItem:[],
            data:[]
        };
    }

    componentWillReceiveProps(nextProps){
        if(nextProps.selectedKeysId&&nextProps.selectedKeysId || nextProps.selectedKeysName&&nextProps.selectedKeysName){
            this.setState({
                selectedKeysId :nextProps.selectedKeysId,
                selectedKeysName : nextProps.selectedKeysName,
                inputValue : nextProps.selectedKeysName,
                data : nextProps.data
            })
        }
    }

    close = (source) =>{
        this.setState({
            showModal : false
        }, ()=>{
            if(source === "confirm"){
                this.props.handleSelectedKeys ({id: [...this.state.selectedKeysId], title : [...this.state.selectedKeysName], item :[...this.state.selectedKeysItem]})
                this.onChangeText();
            }else{
                this.setState({
                    selectedKeysId : [],
                    selectedKeysName :[],
                    selectedKeysName : []
                }) 
            }
        })
    }
    
    onChangeText = (value) =>{
        this.setState({
            inputValue : [...this.state.selectedKeysName]
        })
    }

    onOpenReferModal = (e)=>{
        this.setState({
            showModal : true,
            selectedKeysId : this.props.selectedKeysId || this.state.selectedKeysId,
            sname : this.props.sname || this.state.sname,
            scode :  this.props.scode || this.state.scode,
            pk : this.props.pk || this.state.pk,
            isShowSearchArea : this.props.isShowSearchArea!== undefined ?this.props.isShowSearchArea : this.state.isShowSearchArea,
            children : this.props.children || this.state.children,
            title  : this.props.title || this.state.title,
            selectedKeysItem : this.props.selectedKeysItem ||this.state.selectedKeysItem,
            selectedKeysName : this.props.selectedKeysName ||this.state.selectedKeysName,
        }, ()=>{
            this.props.getData && this.props.getData()
        })
    }

    modalContent = () =>{
       
        let {
            referType,
            data,
            columns
        } = this.props;
        let {
            selectedKeysId,
            sname ,
            scode,
            pk,
            selectedKeysItem
        } = this.state;

        let node = null;
        switch (referType) {
            case "tree":
                node =  <Tree
                            showLine={true}
                            defaultExpandedKeys={selectedKeysId}
                            selectedKeys={selectedKeysId}
                            onSelect={this.onSelect}
                            treeData={data}
                        >
                            {this.loop(data)}
                        </Tree>
                break;
            case "multiSelectTree":
                node = <Tree
                        treeData={data}
                        showLine={true}
                        checkable={true}
                        checkStrictly={true}
                        checkedKeys={selectedKeysId}
                        defaultExpandedKeys={selectedKeysId}
                        defaultCheckedKeys = {selectedKeysId}
                        onCheck={this.mulitOnCheck}
                       // defaultSelectedKeys={selectedKeysId}
                     //   selectedKeys={selectedKeysId}
                       // onSelect={this.mulitOnSelect}
                    >
                        {this.loop(data)}
                    </Tree>
                break;
            case "table":
                node = <MultiSelectTable 
                            columns={columns ?columns :[]}
                            data = {data}
                            showRowNum = {true}
                            multiSelect={{
                                type: "checkbox"
                            }}
                            getSelectedDataFunc= {(selectedList,record,index)=>this.onRowClick(selectedList,record,index)}
                        />
                break;
            case "multiSelectTable":
                node = <MultiSelectTable 
                        columns={columns}
                        data = {data}
                        showRowNum = {true}
                        multiSelect={{
                            type: "checkbox"
                        }}
                        getSelectedDataFunc= {(selectedList,record,index)=>this.getSelectedDataFunc(selectedList,record,index)}
                    />
                break;
        
            default:
                break;
        }
        return (node)
    }
    getSelectedDataFunc = (selectedList,record,index) =>{
        let pks = [];
        selectedList.map((item, index)=>{
            pks.push(item[this.state.pk])
            this.state.selectedKeysItem.map((innerItem, innerIndex)=>{
                if( item[this.state.pk] === innerItemm[this.state.pk]){
                    selectedList[index] = innerItem;
                    selectedList[index].key = item.key;
                    selectedList[index].index = item.index;
                }
            })
        })
       
      
        this.setState({
            selectedKeysItem : [...selectedList],
            pks :[...pks]
        })
    }

    onRowClick = (selectedList,record,index) =>{
         // 控制行点击选中并存当前选中行信息
         let tableData = [...this.state.data];
         tableData.map((item, i) => { // 重置选中状态
             if (index === i) {
                tableData[index]._checked = !tableData[index]._checked;
             } else {
                 item._checked = false;
             }
         });
        this.setState({
            selectedKeysId : [record[this.state.pk]],
            selectedKeysItem : [record],
            data: tableData,
        })
    }
    mulitOnCheck = (selectedKeys, nodeParam) =>{
        let _me = this;
        let title = [];
        if(nodeParam.node.props.children && nodeParam.checked || nodeParam.node.props.children &&nodeParam.selected){
            let res = _me.findPositionAtData(selectedKeys[selectedKeys.length-1], _me.props.data, [])
           
            let obj = _me.getChildrenAttrArr(res, [_me.state.pk, _me.state.sname], [{[_me.state.pk]:[]}, {[_me.state.sname]:[]} ]);
            if(_me.state.selectedKeysId.length ){
                selectedKeys = _me.state.selectedKeysId.concat(obj[0][_me.state.pk]);
                title = _me.state.selectedKeysName.concat( obj[1][_me.state.sname] )
            }else{
                selectedKeys = obj[0][_me.state.pk];
                title =  obj[1][_me.state.sname];
            }
           
        }
        if(!nodeParam.node.props.children ){
            let data = nodeParam.checkedNodes || nodeParam.selectedNodes
            data.map((item)=>{
                title.push(item.props.title)
            })
        }
        _me.setState({
            selectedKeysId : [...selectedKeys],
            selectedKeysName : [...title]
        })

    }
    //根据主键，找到在所有数据中的位置， 并返回他的数据
    /**
     * pk:主键值
     * data:树数据， 或者想要遍历的数组
     * res:最终返回的结果
     */
    findPositionAtData = (pk, data, res) =>{
        data.map((item, index)=>{
            
            if(item[this.state.pk] === pk ||""+item[this.state.pk]+"" === pk){
                res.push(item);
            }
            if(item[this.state.children]){
                this.findPositionAtData(pk, item[this.state.children], res)
            }
        })
        return res;
    }
    /**这是一维数组的遍历， 找到对应字段的值。
     * data:树数据， 或者想要遍历的数组
     * res:最终返回的结果
     * attr：想要获得值的属性，没传， 默认返回当前所有的数据以数组的形式
     */
    getChildrenAttrArr = (data, attr, res) =>{
        data.map((item, index)=>{
            if(this.state.selectedKeysId.indexOf(item[this.state.pk]) === -1){
                attr.map((attrItem, attrIndex)=>{
                    if(item[attrItem] === null){
                        item[attrItem] ="null"
                    }
                    res[attrIndex][attrItem].push(item[attrItem])
                })
            }
            
            if(item[this.state.children]){
                this.getChildrenAttrArr(item[this.state.children], attr, res)
            }
        })
        return res;
    }
    //暂不支持点击树节点， 控制checkbox的状态哦， 有需求在写， 暂时除了组织权限中关联组织， 其他的单据没有此功能。
    mulitOnSelect= (selectedKeys, nodeParam) =>{
        let _me = this;
        if(!nodeParam.selected){
            let index = _me.state.selectedKeysId.indexOf(nodeParam.node.props.eventKey)
            _me.state.selectedKeysId.splice(index, 1);
            _me.state.selectedKeysName.splice(index, 1);
            _me.setState({
                selectedKeysId: [..._me.state.selectedKeysId],
                selectedKeysName: [..._me.state.selectedKeysName]
            })
            return ;
        }
        let selectedKeysTemp = [..._me.state.selectedKeysId];
        let selectedKeysTempName = [..._me.state.selectedKeysName];
        if(selectedKeys.toString()===""){
            return
        }
        if(selectedKeysTemp!==[]){
            if(selectedKeysTemp.lastIndexOf(selectedKeys.toString())===-1){
                selectedKeysTemp.push(selectedKeys.toString());
                selectedKeysTempName.push(nodeParam.node.props.title);
            }else {
                let index = selectedKeysTemp.indexOf(selectedKeys.toString());
                selectedKeysTemp.splice(index,1);
                selectedKeysTempName.splice(index,1);
            }
        }else {
            selectedKeysTemp=[];
            selectedKeysTempName=[];
        }
        _me.setState({
            selectedKeysId : [...selectedKeysTemp],
            selectedKeysName : [...selectedKeysTempName]
        })
        _me.mulitOnCheck(selectedKeysTemp, nodeParam);

    }

    loop = data => data.map((item,index, indexSearchAll) => {
        let titleSearch ='';
        let {
            isShowSearchArea,

            selectedKeysId,
            sname ,
            scode,
            pk,
            children
        } = this.state;
        if(isShowSearchArea){
            titleSearch = this.search(item[sname], index, indexSearchAll);
        }else{
            titleSearch = item[sname]
        }
       
        if (item[children]){
            return (
                <TreeNode 
                    key={item[pk]}
                    title={titleSearch}
                    item = {item}
                >
                    {item[children]? this.loop(item[children]) : null }
                </TreeNode>
            )
        }
        return <TreeNode key={item[pk]} title={titleSearch} item = {item}/>  ;

    });

    search = (item,index, indexSearchAll) =>{
        if(item===undefined){
            return;
        }
        let title=item;
        const indexInValue = this.state.value ? title.indexOf(this.state.value):-1;
        const beforeStr = item.substr(0, indexInValue);
        const afterStr = this.state.value ? item.substr(indexInValue + this.state.value.length):item;

        title = title.indexOf(this.state.value)>-1 ? (
            <span>
                {beforeStr}
                <span className="u-tree-searchable-filter">{this.state.value}</span>
                {afterStr}
                </span>
        ) : <span>{item}</span>;
        this.scrollToAnchor(index, indexInValue, indexSearchAll);
        return title;
    }
    /*搜索的树定位*/
    scrollToAnchor = (index, indexInValue,indexSearchAll) => {
        if(indexInValue!==-1){
            if(index!==undefined){
                indexSearchAll.push(index+1);
            }
       }
       if(indexInValue!==-1){
           if(index===undefined){
               setTimeout(()=>{
                   document.getElementsByClassName("u-tree-title")[0].scrollIntoView();
               },0);
           }else {
               setTimeout(()=>{
                   document.getElementsByClassName("u-tree-title")[indexSearchAll[0]].scrollIntoView();
               },0);
           }
       }

   }
    onSelect = (selectedKeys, nodeParam) =>{
        if(!nodeParam.node.props.item[this.state.pk] ||nodeParam.node.props.item[this.state.pk] === "null"){
            return
        }
        this.setState({
            selectedKeysId : [...selectedKeys],
            selectedKeysName : [nodeParam.node.props.title],
            selectedKeysItem :[nodeParam.node.props.item]
        })
    }

    inputChange = (e) =>{
        
        let value = e.target? e.target.value :e;
        if(!value){
            this.setState({
                selectedKeysId : [],
                selectedKeysName : [],
                selectedKeysItem :[],
                inputValue :[]
            }, ()=>{
                this.props.handleSelectedKeys ({id: [], title : [], item :[]})
            })  
        }
    }
    render() {

        let {
            inputValue,
            showModal,
            selectedKeysId,
            isShowSearchArea,
            title,
        } = this.state;
        return (
            <div>
                <div>
                    <FormControl
                        placeholder = ""
                        value = {!inputValue ? this.props.selectedKeysName :inputValue}
                        onClick = {this.onOpenReferModal}
                        suffix={inputValue.length || this.props.selectedKeysName.length  ? null: <Icon type='uf-listwithdots'/> }
                        showClose = {inputValue.length || this.props.selectedKeysName.length ? true :false}
                        onChange = {this.inputChange}
                    />

                </div> 
                <Modal
                    backdrop = {false}
                    show = {showModal}
                    onHide = {this.close}
                    size = {"lg"}
                >
                    <Modal.Header closeButton className={"targetModalheader"}>
                        <Modal.Title>{title ? title :'参照列表'}</Modal.Title>
                    </Modal.Header>
                    <Modal.Body>
                       {
                           isShowSearchArea?
                            <div  className={'search-header'}>
                                <div className={'search-header-search'}>
                                    <FormControl
                                        value={""}
                                        onChange = {this.onSearch}
                                        placeholder="请输入要查询的内容"
                                        emptyText={() => '暂无数据'}
                                        className={'searchFormControl'}
                                        showClose = {true}
                                    />
                                    <Icon className="search-icon" type='uf uf-search-light' />
                                </div>
                            </div>:
                            null
                       }

                        {this.modalContent()}
                    </Modal.Body>
                    <Modal.Footer className={"footerButton"}>
                        <Button onClick={()=>this.close()} className = {"cancel"} >取消</Button>
                            <Button 
                                onClick={()=>this.close("confirm")} 
                                className = {"confirm"} 
                             //   disabled ={selectedKeysId.length ? false: true}
                                bordered
                            >确认</Button>
                    </Modal.Footer>
                </Modal>
            </div>
        );
    }
}
export default CommonTreeReferStruc;
